# -*- coding: utf-8 -*-
import logging , sys , traceback
import time
import os


class DateFileHandler(logging.FileHandler):
    def __init__(self, filename, mode="a" ):
        self.bf = filename
        self.curDate = time.strftime( '%Y%m%d' , time.localtime())
        self.mode = mode
        t = time.time()
        filename = filename + '.' + self.curDate
        logging.FileHandler.__init__(self, filename, mode)

    def emit(self, record):
        cd = time.strftime( '%Y%m%d' , time.localtime())
        if cd != self.curDate:
            self.stream.close()
            self.curDate = cd
            self.stream = open(self.bf + '.' + cd , self.mode )
        logging.FileHandler.emit(self, record)

class DatabaseHandler( logging.Handler ):
    def __init__( self , cur , prefix ):
        """
            @param cur ���ݿ�������
            @param prefix ��־�����ʽΪyyyy-mm-dd[xx��Ŀ]��̨���ݴ���
        """
        logging.Handler.__init__( self )
        self.cur = cur 
        self.prefix = prefix
        self.fmtsql = """insert into gl_xtczrz( hydm , fssj , jb , btxx , xxxx ) 
values ( 'back' , sysdate , %%d , '%s' , '%%s' )""" %  prefix
        
    def emit( self , record ):
        sql = self.fmtsql % ( record.levelno / 10 , record.message )
        if self.cur:
            self.cur.execute( sql )
    
    def filter( self , record ):
        if record.levelno > logging.INFO:
            return True
        return False
    
    def close( self ):
        self.cur.close()
        self.cur = None


class LOG( object ):
    def __init__( self, name = None , screen = False , thread = True, logdir = None ):
        self.logname = name
        self.screen = screen
        self.thread = thread
        self.logdir = logdir
        
    def init_logger( self ):
        logobj = logging.getLogger( self.logname )
        # �ж��Ƿ���Ҫ����,��־�Ѵ���������
        if logobj.handlers:
            return  logobj
        
        # ��ʼ����־�ļ�������
        fn = '%s.log' % self.logname
        hdlr = DateFileHandler( os.path.join( self.logdir , fn ) )
        fmts = '%(asctime)s ' + ( 'T%(thread)d ' if self.thread else '' ) +  '%(levelname)s %(message)s'
        formatter = logging.Formatter( fmts )
        hdlr.setFormatter(formatter)
        logobj.addHandler( hdlr )
        
        if self.screen:
            # ��ʼ����Ļ��ӡ������
            hdlr = logging.StreamHandler()
            fmts = '%(asctime)s %(name)s��' + ( 'T%(thread)d ' if self.thread else '' ) + '%(levelname)s %(message)s'
            formatter = logging.Formatter( fmts )
            hdlr.setFormatter(formatter)
            logobj.addHandler( hdlr )

        logobj.setLevel( logging.DEBUG )
        return logobj

    def _fmt_msg( self, *args , **kwargs ):
        if len( args ) > 1:
            msg = args[0] % args[1:]
        elif len( args ) == 1:
            msg = args[0]
        else:
            msg = ''
        
        block = kwargs.get( 'block' )
        if type(block) is str:
            # �ǿ���־
            bin = kwargs.get( 'bin' , True )
            if bin:
                block = to_hex( block )
        
        if block:
            block = '\n'+'='*40+'\n'+block+ ('\n' if block[-1] != '\n' else '' ) +'='*40 + '\n'
        elif msg[-1] == '\n':
            block = ''
        else:
            block = '\n'
        
        msg = msg + block
        if msg[-1] == '\n':
            msg = msg[:-1]
        return msg
        
    def debug( self , *args , **kwargs ):
        logger = self.init_logger()
        logger.debug( self._fmt_msg( *args , **kwargs ) )

    def info( *args , **kwargs ):
        logger = self.init_logger()
        logger.info( self._fmt_msg( *args , **kwargs ) )
            
    def warning( *args , **kwargs ):
        logger = self.init_log()
        logger.warning( self._fmt_msg( *args , **kwargs ) )
            
    def error( *args , **kwargs ):
        logger = self.init_log()
        logger.error( self._fmt_msg( *args , **kwargs ) )
            
    def critical( *args , **kwargs ):
        logger = self.init_log()
        logger.critical( self._fmt_msg( *args , **kwargs ) )

    def exception( *args , **kwargs ):
        logger = self.init_log()
        #exc_msg = traceback2.format_exc( show_locals = True )
        exc_msg = traceback.format_exc()
        args = list( args )
        if args:
            args[0] += '\n%s'
        else:
            args.append( '%s' )
        args.append( exc_msg )
        logger.error(self._fmt_msg( *args , **kwargs ) )
        return ''